package com.phiture.erp.purchase.web.controller.admin;

import cn.iocoder.yudao.framework.common.util.collection.MapUtils;
import cn.iocoder.yudao.module.system.api.dept.DeptApi;
import cn.iocoder.yudao.module.system.api.dept.dto.DeptRespDTO;
import cn.iocoder.yudao.module.system.api.user.AdminUserApi;
import cn.iocoder.yudao.module.system.api.user.dto.AdminUserRespDTO;
import com.phiture.erp.basic.api.pojo.resp.ErpMaterialInfoResp;
import com.phiture.erp.basic.api.service.ErpMaterialApi;
import com.phiture.erp.purchase.core.pojo.vo.ErpPurchaseRequestItemsRespVO;
import com.phiture.erp.purchase.core.pojo.vo.ErpPurchaseRequestPageReqVO;
import com.phiture.erp.purchase.core.pojo.vo.ErpPurchaseRequestRespVO;
import com.phiture.erp.purchase.core.pojo.vo.ErpPurchaseRequestSaveReqVO;
import com.phiture.erp.purchase.core.service.ErpPurchaseRequestService;
import com.phiture.erp.purchase.dal.entity.ErpPurchaseRequestDO;
import com.phiture.erp.purchase.dal.entity.ErpPurchaseRequestItemsDO;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
import org.springframework.validation.annotation.Validated;
import org.springframework.security.access.prepost.PreAuthorize;
import io.swagger.v3.oas.annotations.tags.Tag;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.Operation;

import javax.validation.*;
import javax.servlet.http.*;
import java.util.*;
import java.io.IOException;

import cn.iocoder.yudao.framework.common.pojo.PageParam;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success;

import cn.iocoder.yudao.framework.excel.core.util.ExcelUtils;

import cn.iocoder.yudao.framework.apilog.core.annotation.ApiAccessLog;
import static cn.iocoder.yudao.framework.apilog.core.enums.OperateTypeEnum.*;
import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertSet;

@Tag(name = "管理后台 - 采购申请单")
@RestController
@RequestMapping("/erp/purchase-request")
@Validated
public class ErpPurchaseRequestController {

    @Resource
    private ErpPurchaseRequestService purchaseRequestService;

    @Resource
    private ErpMaterialApi erpMaterialApi;

    @Resource
    private AdminUserApi adminUserApi;
    @Resource
    private DeptApi deptApi;

    @PostMapping("/create")
    @Operation(summary = "创建采购申请单")
    @PreAuthorize("@ss.hasPermission('erp:purchase-request:create')")
    public CommonResult<Long> createPurchaseRequest(@Valid @RequestBody ErpPurchaseRequestSaveReqVO createReqVO) {
        return success(purchaseRequestService.createPurchaseRequest(createReqVO));
    }

    @PutMapping("/update")
    @Operation(summary = "更新采购申请单")
    @PreAuthorize("@ss.hasPermission('erp:purchase-request:update')")
    public CommonResult<Boolean> updatePurchaseRequest(@Valid @RequestBody ErpPurchaseRequestSaveReqVO updateReqVO) {
        purchaseRequestService.updatePurchaseRequest(updateReqVO);
        return success(true);
    }

    @PutMapping("/update-status")
    @Operation(summary = "更新采购申请单的状态")
    @PreAuthorize("@ss.hasPermission('erp:purchase-request:update-status')")
    public CommonResult<Boolean> updatePurchaseOrderStatus(@RequestParam("id") Long id,
                                                           @RequestParam("status") Integer status) {
        purchaseRequestService.updatePurchaseRequestStatus(id, status);
        return success(true);
    }

    @DeleteMapping("/delete")
    @Operation(summary = "删除采购申请单")
    @Parameter(name = "id", description = "编号", required = true)
    @PreAuthorize("@ss.hasPermission('erp:purchase-request:delete')")
    public CommonResult<Boolean> deletePurchaseRequest(@RequestParam("id") Long id) {
        purchaseRequestService.deletePurchaseRequest(id);
        return success(true);
    }

    @GetMapping("/get")
    @Operation(summary = "获得采购申请单")
    @Parameter(name = "id", description = "编号", required = true, example = "1024")
    @PreAuthorize("@ss.hasPermission('erp:purchase-request:query')")
    public CommonResult<ErpPurchaseRequestRespVO> getPurchaseRequest(@RequestParam("id") Long id) {
        ErpPurchaseRequestDO purchaseRequest = purchaseRequestService.getPurchaseRequest(id);
        return success(BeanUtils.toBean(purchaseRequest, ErpPurchaseRequestRespVO.class));
    }

//    @GetMapping("/page")
//    @Operation(summary = "获得采购申请单分页")
//    @PreAuthorize("@ss.hasPermission('erp:purchase-request:query')")
//    public CommonResult<PageResult<ErpPurchaseRequestRespVO>> getPurchaseRequestPage(@Valid ErpPurchaseRequestPageReqVO pageReqVO) {
//        PageResult<ErpPurchaseRequestDO> pageResult = purchaseRequestService.getPurchaseRequestPage(pageReqVO);
//
//        Map<Long, String> materialNameMap = new HashMap<>();
//        // 根据采购订单ID查询申请单明细
//        pageResult.getList().forEach(purchaseRequest -> {
//            List<ErpPurchaseRequestItemsDO> purchaseRequestItemsList = purchaseRequestService.getPurchaseRequestItemsListByRequestId(purchaseRequest.getId());
//            // 根据所有申请单明细中的物料ID查询物料信息，把所有物料的名称以逗号拼接存入采购申请单的物料名称字段
//            Map<Long, ErpMaterialInfoResp> materialMap = erpMaterialApi.getMaterialMap(
//                    convertSet(purchaseRequestItemsList, ErpPurchaseRequestItemsDO::getMaterialId));
//            StringBuilder materialName = new StringBuilder();
//            for (ErpPurchaseRequestItemsDO purchaseRequestItems : purchaseRequestItemsList) {
//                ErpMaterialInfoResp material = materialMap.get(purchaseRequestItems.getMaterialId());
//                if (material != null) {
//                    materialName.append(material.getName()).append(",");
//                }
//            }
//            // 去掉最后一个逗号
//            if (materialName.length() > 0) {
//                materialName.deleteCharAt(materialName.length() - 1);
//            }
//            // 申请单的ID，物料名称存入map中
//            materialNameMap.put(purchaseRequest.getId(), materialName.toString());
//        });
//
//        // 根据申请单中的申请人ID批量查出申请人姓名
//        Map<Long, AdminUserRespDTO> userMap = adminUserApi.getUserMap(
//                convertSet(pageResult.getList(), purchaseRequest -> purchaseRequest.getPersonId()));
//
//        // 获取申请部门名称
//        Map<Long, DeptRespDTO> deptMap = deptApi.getDeptMap(
//                convertSet(pageResult.getList(), ErpPurchaseRequestDO::getDeptId));
//
//        return success(BeanUtils.toBean(pageResult, ErpPurchaseRequestRespVO.class, purchaseRequest -> {
//            // 申请人姓名
//            MapUtils.findAndThen(userMap, purchaseRequest.getPersonId(), user -> purchaseRequest.setPersonName(user.getNickname()));
//            // 申请部门名称
//            MapUtils.findAndThen(deptMap, purchaseRequest.getDeptId(), dept -> purchaseRequest.setDeptName(dept.getName()));
//            // 物料名称
//            MapUtils.findAndThen(materialNameMap, purchaseRequest.getId(), name -> purchaseRequest.setMaterialName(name));
//        }));
//    }


//    @GetMapping("/page")
//    @Operation(summary = "获得采购申请单分页")
//    @PreAuthorize("@ss.hasPermission('erp:purchase-request:query')")
//    public CommonResult<PageResult<ErpPurchaseRequestRespVO>> getPurchaseRequestPage(@Valid ErpPurchaseRequestPageReqVO pageReqVO) {
//        PageResult<ErpPurchaseRequestRespVO> pageResult = purchaseRequestService.getPurchaseRequestPage(pageReqVO);
//
//        Map<Long, String> materialNameMap = new HashMap<>();
//        // 根据采购申请ID查询申请单明细
//        pageResult.getList().forEach(purchaseRequest -> {
//            List<ErpPurchaseRequestItemsDO> purchaseRequestItemsList = purchaseRequestService.getPurchaseRequestItemsListByRequestId(purchaseRequest.getId());
//            // 根据所有申请单明细中的物料ID查询物料信息，把所有物料的名称以逗号拼接存入采购申请单的物料名称字段
//            Map<Long, ErpMaterialInfoResp> materialMap = erpMaterialApi.getMaterialMap(
//                    convertSet(purchaseRequestItemsList, ErpPurchaseRequestItemsDO::getMaterialId));
//            StringBuilder materialName = new StringBuilder();
//            for (ErpPurchaseRequestItemsDO purchaseRequestItems : purchaseRequestItemsList) {
//                ErpMaterialInfoResp material = materialMap.get(purchaseRequestItems.getMaterialId());
//                if (material != null) {
//                    materialName.append(material.getName()).append(",");
//                }
//            }
//            // 去掉最后一个逗号
//            if (materialName.length() > 0) {
//                materialName.deleteCharAt(materialName.length() - 1);
//            }
//            // 申请单的ID，物料名称存入map中
//            materialNameMap.put(purchaseRequest.getId(), materialName.toString());
//        });
//
//        // 根据申请单中的申请人ID批量查出申请人姓名
//        Map<Long, AdminUserRespDTO> userMap = adminUserApi.getUserMap(
//                convertSet(pageResult.getList(), purchaseRequest -> purchaseRequest.getPersonId()));
//
//        // 获取申请部门名称
//        Map<Long, DeptRespDTO> deptMap = deptApi.getDeptMap(
//                convertSet(pageResult.getList(), ErpPurchaseRequestRespVO::getDeptId));
//
//        return success(BeanUtils.toBean(pageResult, ErpPurchaseRequestRespVO.class, purchaseRequest -> {
//            // 申请人姓名
//            MapUtils.findAndThen(userMap, purchaseRequest.getPersonId(), user -> purchaseRequest.setPersonName(user.getNickname()));
//            // 申请部门名称
//            MapUtils.findAndThen(deptMap, purchaseRequest.getDeptId(), dept -> purchaseRequest.setDeptName(dept.getName()));
//            // 物料名称
//            MapUtils.findAndThen(materialNameMap, purchaseRequest.getId(), name -> purchaseRequest.setMaterialName(name));
//        }));
//    }


    @GetMapping("/page")
    @Operation(summary = "获得采购申请单分页（获取采购申请明细行）")
    @PreAuthorize("@ss.hasPermission('erp:purchase-request:query')")
    public CommonResult<PageResult<ErpPurchaseRequestRespVO>> getPurchaseRequestPage(@Valid ErpPurchaseRequestPageReqVO pageReqVO) {
        PageResult<ErpPurchaseRequestRespVO> pageResult = purchaseRequestService.getPurchaseRequestPage(pageReqVO);

        Map<Long, ErpMaterialInfoResp> materialMap = erpMaterialApi.getMaterialMap(
                convertSet(pageResult.getList(), ErpPurchaseRequestRespVO::getMaterialId));

        // 根据申请单中的申请人ID批量查出申请人姓名
        Map<Long, AdminUserRespDTO> userMap = adminUserApi.getUserMap(
                convertSet(pageResult.getList(), purchaseRequest -> purchaseRequest.getPersonId()));

        // 获取申请部门名称
        Map<Long, DeptRespDTO> deptMap = deptApi.getDeptMap(
                convertSet(pageResult.getList(), ErpPurchaseRequestRespVO::getDeptId));

        return success(BeanUtils.toBean(pageResult, ErpPurchaseRequestRespVO.class, purchaseRequest -> {
            // 申请人姓名
            MapUtils.findAndThen(userMap, purchaseRequest.getPersonId(), user -> purchaseRequest.setPersonName(user.getNickname()));
            // 申请部门名称
            MapUtils.findAndThen(deptMap, purchaseRequest.getDeptId(), dept -> purchaseRequest.setDeptName(dept.getName()));
            // 物料名称
            MapUtils.findAndThen(materialMap, purchaseRequest.getMaterialId(), material -> {
                purchaseRequest.setMaterialName(material.getName());
                purchaseRequest.setUnitName(material.getUnitName());
            });
        }));
    }

    @GetMapping("/export-excel")
    @Operation(summary = "导出采购申请单 Excel")
    @PreAuthorize("@ss.hasPermission('erp:purchase-request:export')")
    @ApiAccessLog(operateType = EXPORT)
    public void exportPurchaseRequestExcel(@Valid ErpPurchaseRequestPageReqVO pageReqVO,
              HttpServletResponse response) throws IOException {
        pageReqVO.setPageSize(PageParam.PAGE_SIZE_NONE);
        List<ErpPurchaseRequestRespVO> list = purchaseRequestService.getPurchaseRequestPage(pageReqVO).getList();
        // 导出 Excel
        ExcelUtils.write(response, "采购申请单.xls", "数据", ErpPurchaseRequestRespVO.class,
                        BeanUtils.toBean(list, ErpPurchaseRequestRespVO.class));
    }

    // ==================== 子表（采购申请单明细） ====================

    @GetMapping("/purchase-request-items/list-by-request-id")
    @Operation(summary = "获得采购申请单明细列表")
    @Parameter(name = "requestId", description = "申请单ID")
    @PreAuthorize("@ss.hasPermission('erp:purchase-request:query')")
    public CommonResult<List<ErpPurchaseRequestItemsRespVO>> getPurchaseRequestItemsListByRequestId(@RequestParam("requestId") Long requestId) {
        List<ErpPurchaseRequestItemsDO> result = purchaseRequestService.getPurchaseRequestItemsListByRequestId(requestId);

        Map<Long, ErpMaterialInfoResp> materialMap = erpMaterialApi.getMaterialMap(
                convertSet(result, ErpPurchaseRequestItemsDO::getMaterialId));
        return success(BeanUtils.toBean(result, ErpPurchaseRequestItemsRespVO.class, requestItems ->{
            MapUtils.findAndThen(materialMap, requestItems.getMaterialId(), material -> requestItems.setMaterialNumber(material.getBarCode()));
            MapUtils.findAndThen(materialMap, requestItems.getMaterialId(), material -> requestItems.setMaterialName(material.getName()));
        }));
    }

}